/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package byzantine.views;

import byzantine.ByzantineModel;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Toolkit;
import javax.swing.BorderFactory;
import javax.swing.Box;
import javax.swing.JLabel;
import javax.swing.JPanel;

/**
 *
 * @author rpathan
 */
public class StatisticsView extends JPanel implements View {

    private static final String numGeneralsString = "Generals: ";
    private static final String numLoyalString = "Loyal: ";
    private static final String numTraitorsString = "Traitors: ";
    private static final String numRoundsString = "Rounds: ";
    private static final String numMessageString = "Messages Sent: ";
    private static final String simulationTimeString = "Runtime: ";
    private static final String unitsString = " s";
    private static final String numAttackingString = "Generals Attacking: ";
    private static final String numRetreatingString = "Generals Retreating: ";
    private static final String algorithmOutcomeString = "Algorithm Outcome: ";
    private static final Font font = new Font("Dialog", Font.BOLD, 11);

    //private int width;
    //private int height;
    //private int nameToLabelSpacing;
    //private int labelToLabelSpacing;

    private int width = 250;
    private int height = 200;
    private int nameToLabelSpacing = 10;
    private int labelToLabelSpacing = 5;

    ByzantineModel model;
    private JLabel panelName;
    private JLabel numGeneralsLabel;
    private JLabel numLoyalLabel;
    private JLabel numTraitorsLabel;
    private JLabel numRoundsLabel;
    private JLabel numMessagesLabel;
    private JLabel simulationTimeLabel;
    private JLabel numAttackingLabel;
    private JLabel numRetreatingLabel;
    private JLabel algorithmOutcomeLabel;

    public StatisticsView(ByzantineModel model) {
        this.model = model;
        model.addObserver(this);
/*
        Toolkit t = Toolkit.getDefaultToolkit();
        Dimension screenSize = t.getScreenSize();
        width = (int)((screenSize.width - 10) * 0.185);
        height = (int)((screenSize.height - 100) * 0.27);
        nameToLabelSpacing = (int)(height * 0.10);
        labelToLabelSpacing = (int)(height * 0.08);
*/
        initializeView();
    }

    private void initializeView() {

        panelName = new JLabel("Statistics");
        panelName.setAlignmentX(Component.CENTER_ALIGNMENT);
        panelName.setAlignmentY(Component.CENTER_ALIGNMENT);
        panelName.setFont(font);

        numGeneralsLabel = new JLabel(numGeneralsString + model.getNumGenerals());
        numGeneralsLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numGeneralsLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numGeneralsLabel.setFont(font);

        numLoyalLabel = new JLabel(numLoyalString + model.getNumLoyal());
        numLoyalLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numLoyalLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numLoyalLabel.setFont(font);

        numTraitorsLabel = new JLabel(numTraitorsString + model.getNumTraitors());
        numTraitorsLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numTraitorsLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numTraitorsLabel.setFont(font);
        
        numRoundsLabel = new JLabel(numRoundsString + model.getNumRounds());
        numRoundsLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numRoundsLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numRoundsLabel.setFont(font);

        numMessagesLabel = new JLabel(numMessageString + model.getNumMessages());
        numMessagesLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numMessagesLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numMessagesLabel.setFont(font);

        simulationTimeLabel = new JLabel(simulationTimeString + (double)model.getSimulationTime()/1000000000.0 + unitsString);
        simulationTimeLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        simulationTimeLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        simulationTimeLabel.setFont(font);

        numMessagesLabel = new JLabel(numMessageString + model.getNumMessages());
        numMessagesLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numMessagesLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numMessagesLabel.setFont(font);

        numAttackingLabel = new JLabel(numAttackingString + model.getNumAttacking());
        numAttackingLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numAttackingLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numAttackingLabel.setFont(font);

        numRetreatingLabel = new JLabel(numRetreatingString + model.getNumRetreating());
        numRetreatingLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        numRetreatingLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        numRetreatingLabel.setFont(font);

        algorithmOutcomeLabel = new JLabel(algorithmOutcomeString + "n/a");
        algorithmOutcomeLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
        algorithmOutcomeLabel.setAlignmentY(Component.CENTER_ALIGNMENT);
        algorithmOutcomeLabel.setFont(font);

        Box box1 = Box.createVerticalBox();
        box1.setAlignmentX(Component.CENTER_ALIGNMENT);
        box1.setAlignmentY(Component.CENTER_ALIGNMENT);
        box1.add(panelName);
        box1.add(Box.createVerticalStrut(nameToLabelSpacing));
        box1.add(numGeneralsLabel);
        box1.add(numLoyalLabel);
        box1.add(numTraitorsLabel);
        box1.add(Box.createVerticalStrut(labelToLabelSpacing));
        box1.add(numRoundsLabel);
        box1.add(numMessagesLabel);
        box1.add(simulationTimeLabel);
        box1.add(Box.createVerticalStrut(labelToLabelSpacing));
        box1.add(numAttackingLabel);
        box1.add(numRetreatingLabel);
        box1.add(algorithmOutcomeLabel);

        this.add(box1);

        setBorder(BorderFactory.createEtchedBorder());
    }

    private void populateStatistics() {

        numGeneralsLabel.setText(numGeneralsString + model.getNumGenerals().toString());
        numLoyalLabel.setText(numLoyalString + model.getNumLoyal().toString());
        numTraitorsLabel.setText(numTraitorsString + model.getNumTraitors().toString());
        numRoundsLabel.setText(numRoundsString + model.getNumRounds().toString());
        numMessagesLabel.setText(numMessageString + model.getNumMessages().toString());
        simulationTimeLabel.setText(simulationTimeString + (double)model.getSimulationTime()/1000000000.0 + unitsString);
        numAttackingLabel.setText(numAttackingString + model.getNumAttacking());
        numRetreatingLabel.setText(numRetreatingString + model.getNumRetreating());
        if (model.getAlgorithmOutcome() == true && model.isSimulationRunning()) {
            algorithmOutcomeLabel.setText(algorithmOutcomeString + "Success");
        } else if (model.getAlgorithmOutcome() == false && model.isSimulationRunning()) {
            algorithmOutcomeLabel.setText(algorithmOutcomeString + "Failure");
        } else {
            algorithmOutcomeLabel.setText(algorithmOutcomeString + "n/a");
        }
        
    }

    public void valueChanged() {
        populateStatistics();
    }

    @Override
    public Dimension getPreferredSize() {
        return new Dimension(width, height);
    }
}
